#ifndef CLIENTCONTEXT_H
#define CLIENTCONTEXT_H

#include <WinSock2.h>
#include <Windows.h>
#include "Log.h"
#include "HttpRequestPack.h"
#include "HttpResponseHeader.h"
#include "ClientContextExt.h"
#include "InsTempContext.h"

class ITransHandler;

class ClientContext
{
public:
	ClientContext();

	~ClientContext();

	ITransHandler* CurrentHandler()
	{
		return m_currentHandler;
	}

	ITransHandler* SetCurrentHandler(ITransHandler *handler)
	{
		ITransHandler *temp=m_currentHandler;
		m_currentHandler=handler;
		return temp;
	}

	unsigned int ThreadRefCount()
	{
		return m_threadRefCount;
	}

	void SetThreadRefCount(unsigned int value)
	{
		m_threadRefCount=value;
	}

	bool NeedRelease()
	{
		return m_needRelease;
	}

	void SetNeedRelease(bool value)
	{
		m_needRelease=value;
	}

	SOCKET SrcSock()
	{
		return m_srcSock;
	}

	void SetSrcSock(SOCKET sock)
	{
		m_srcSock=sock;
	}

	SOCKET DestSock()
	{
		return m_destSock;
	}

	void SetDestSock(SOCKET sock)
	{
		m_destSock=sock;
	}

	WSABUF* Buffer()
	{
		return &m_buffer;
	}

	OVERLAPPED* OVL()
	{
		return &m_ovl;
	}

	WSABUF* WeakRefBuffer()
	{
		return &m_weakRefBuf;;
	}

	unsigned int SequenceNo()
	{
		return m_sequenceNo;
	}

	void SetSequenceNo(unsigned int number)
	{
		m_sequenceNo=number;
	}

	HttpRequestPack& HttpRequest()
	{
		return m_httpRequest;
	}

	HttpResponseHeader& HttpResponseHeaderData()
	{
		return *m_httpResponseHeader;
	}

	std::string::size_type PartialTransIndex()
	{
		return m_partialTransIndex;
	}

	void SetPartialTransIndex(std::string::size_type index)
	{
		m_partialTransIndex=index;
	}

	long long& TranslatedFileIndex()
	{
		return m_translatedFileIndex;
	}

	long long& MaxFileIndex()
	{
		return m_maxFileIndex;
	}

	ClientContextExt& ExtContext()
	{
		return m_extContext;
	}

	void InitializeInsteadContext();

	void FreeInsteadContext();

	//void ResetDestinationConnection();

	void ReplaceDestinationWithInsteadContext();

	InsTempContext& InsteadContext()
	{
		return *m_insContext;
	}
private:
	static log4cplus::Logger log;

	void InitAsyncParam(OVERLAPPED*,WSABUF*);

	ITransHandler *m_currentHandler;

	unsigned int m_sequenceNo;

	unsigned int m_threadRefCount;

	bool m_needRelease;

	SOCKET m_srcSock;

	SOCKET m_destSock;

	OVERLAPPED m_ovl;

	WSABUF m_buffer;

	WSABUF m_weakRefBuf;

	HttpRequestPack m_httpRequest;

	HttpResponseHeader *m_httpResponseHeader;

	std::string::size_type m_partialTransIndex;

	long long m_translatedFileIndex;

	long long m_maxFileIndex;

	ClientContextExt m_extContext;

	InsTempContext *m_insContext;

#if _DEBUG

public:
	HANDLE m_debugFileHandle;

#endif
};

#endif